<template>
  <div class="home-config-container app-container bg-grey">
    <!-- 搜索区域 -->

    <div v-show="showSearch">
      
      <el-row :gutter="12" class="bg-fff bor-r-10 p20 mb20" style="padding-bottom: 5px;">
        <el-col :span="12">
          <el-form :model="queryP" ref="queryForm" size="small" :inline="true" v-show="showSearch">
            <el-form-item label="标题" prop="title" class="search-item">
              <el-input
                v-model="queryP.title"
                placeholder="请输入标题"
                clearable
                suffix-icon="el-icon-search"
                @keyup.enter.native="handleQuery"
              />
            </el-form-item>
            <el-form-item class="search-operate">
              <el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button>
              <el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
            </el-form-item>
          </el-form>
        </el-col>
        <el-col :span="1.5" class="right">
          <el-button
            type="primary"
            plain
            icon="el-icon-plus"
            size="small"
            @click="handleAdd"
            v-hasPermi="['demo:homeConfig:add']"
          >新增配置</el-button>
        </el-col>
      </el-row>
      
    </div>
    <div class="h45">
      <right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar>
    </div>

    <!-- 配置卡片区域 -->
    <div class="config-grid">
      <el-row :gutter="20">
        <el-col 
          v-for="(item, index) in configList" 
          :key="item.id"
          :xs="24" :sm="12" :md="8" :lg="6"
        >
          <div class="config-card">
            <div class="card-header">
              <span class="card-index">#{{ index + 1 }}</span>
              <el-tag 
                :type="item.type === '50' ? 'primary' : 'success'"
                size="mini"
                effect="plain"
              >
                {{ item.type === '50' ? '单倍高度' : '双倍高度' }}
              </el-tag>
            </div>
            
            <div class="card-body">
              <el-row>
                <el-col :span="18">
                  <h4 class="card-title">{{ item.title }}</h4>
                  <div class="card-meta">
                    <span class="meta-label">对话标题：</span>
                    <el-tooltip :content="item.interlocutionTitle" placement="top">
                      <span class="meta-value">{{ item.interlocutionTitle }}</span>
                    </el-tooltip>
                  </div>
                  <div class="card-meta">
                    <span class="meta-label">RAG助手：</span>
                    <el-tooltip :content="item.assisId" placement="top">
                      <span class="meta-value">{{ item.assisId }}</span>
                    </el-tooltip>
                  </div>
                  <div class="card-meta">
                    <span class="meta-label">关联集合：</span>
                    <el-tooltip :content="item.collectionName" placement="top">
                      <span class="meta-value">{{ item.collectionName }}</span>
                    </el-tooltip>
                  </div>
                </el-col>
                <el-col :span="6">
                  <div :class="item.icon" style="font-size: 60px;float: inline-end;color: #3d9cff;;"></div>
                </el-col>
              </el-row>
            </div>

            <div class="card-footer">
              <div class="status-wrapper">
                <el-switch
                  v-model="item.status === '0'"
                  active-color="#13ce66"
                  inactive-color="#dcdfe6"
                  active-text="启用"
                  inactive-text="停用"
                  @change="handleStatusChange(item)"
                />
              </div>
              <div class="action-wrapper">
                <el-button
                  type="text"
                  icon="el-icon-edit"
                  @click="handleUpdate(item)"
                >编辑</el-button>
                <el-button
                  type="text"
                  icon="el-icon-delete"
                  @click="handleDelete(item)"
                  class="delete-btn"
                >删除</el-button>
              </div>
            </div>
          </div>
        </el-col>
      </el-row>
    </div>

    <!-- 分页 -->
    <div class="bg-grey page-posi-div" v-show="total>0">
      <div class="bg-fff bor-r-10 p10 pb20">
        <pagination
        :total="total"
        :page.sync="queryP.pageNum"
        :limit.sync="queryP.limit"
        @pagination="getList"
        />
      </div>
    </div>
  


    
    <!-- 编辑弹窗 -->
    <el-dialog :title="title" :visible.sync="open" width="50vw" class="config-dialog">
      <el-steps :active="active" finish-status="success">
        <el-step title="基础配置" icon="el-icon-edit"></el-step>
        <el-step title="向量数据库" icon="el-icon-s-home"></el-step>
        <el-step title="参考文档" icon="el-icon-s-order"></el-step>
        <el-step title="助手配置" icon="el-icon-s-custom"></el-step>
      </el-steps>
      <el-form v-show="active === 0" ref="form" :model="form" :rules="rules" label-width="100px" label-position="top">
        <el-row :gutter="20">
          <el-col :span="24">
            <el-form-item label="配置标题：" prop="title">
              <el-input v-model="form.title" placeholder="请输入标题" clearable />
            </el-form-item>
          </el-col>
          <el-col :span="24">
            <el-form-item label="对话标题：" prop="interlocutionTitle">
              <el-input v-model="form.interlocutionTitle" placeholder="请输入对话标题" clearable />
            </el-form-item>
          </el-col>
          <el-col :span="24">
            <el-form-item label="卡片类型：" prop="type">
              <el-select v-model="form.type" placeholder="请选择类型" clearable style="width: 100%;">
                <el-option
                  v-for="dict in typeOptions"
                  :key="dict.dictValue"
                  :label="dict.dictLabel"
                  :value="dict.dictValue"
                />
              </el-select>
            </el-form-item>
          </el-col>
          <el-col :span="24">
            <el-form-item label="唯一标识：" prop="key">
              <el-input v-model="form.key" placeholder="请输入标识" clearable />
            </el-form-item>
          </el-col>

          <el-col :span="24">
            <el-form-item label="开屏提示词：" prop="cueWord">
              <el-input v-model="form.cueWord" placeholder="请输入开屏提示词" clearable />
            </el-form-item>
          </el-col>
          
          <el-col :span="24">
            <el-form-item label="选择图标：" prop="icon">
              <el-popover
                placement="bottom-start"
                width="600"
                trigger="click"
                @show="$refs['iconSelect'].reset()"
              >
                <IconSelect ref="iconSelect" @selected="selected" :active-icon="form.icon" />
                <el-input slot="reference" v-model="form.icon" placeholder="点击选择图标" readonly>
                  <i
                    v-if="form.icon"
                    slot="prefix"
                    :class="form.icon"
                    style="width: 25px;"
                  />
                  <i v-else slot="prefix" class="el-icon-search el-input__icon" />
                </el-input>
              </el-popover>
            </el-form-item>
          </el-col>
          <!-- <el-col :span="24">
            <el-form-item label="跳转路径：" prop="url">
              <el-input v-model="form.url" placeholder="请输入跳转路径" clearable />
            </el-form-item>
          </el-col> -->
        </el-row>
      </el-form>
      <xiang-liang v-show="active === 1" ref="xiangLiang" :initial-data="xiangLiangForm" :is-dis="xiangLiangIsDis"/>
      <add-docs v-show="active === 2" ref="addData" :initial-data="addDataForm"/>
      <agent-form v-show="active === 3" ref="agent" :initial-data="agentForm" :is-dis="agentFormIsDis"/>
      <template #footer>
        <div class="dialog-footer">
          <el-button @click="cancel">取 消</el-button>
          <el-button v-if="active > 0" @click="active--">上一步</el-button>
          <el-button v-if="active < 3" @click="active++">下一步</el-button>
          <el-button v-if="active === 3" type="primary" @click="submitForm">确 定</el-button>
        </div>
      </template>
    </el-dialog>
  </div>
</template>
<script>
import { listConfig, getConfig, delConfig, addConfig, updateConfig } from "@/api/wenda/homeConfig";
import langC from "@/api/wenda/langChain";
import AgentForm from "@/views/agent/AgentForm";
import XiangLiang from "@/views/agent/XiangLiang";
import AddDocs from "@/views/agent/AddDocs";
// import IconSelect from './IconSelect'
// import IconSelect from "@/components/IconSelect";
import IconSelect from "./ElementIconSelect";

export default {
  name: "homeConfig",
  components: {
    AgentForm,
    XiangLiang,
    AddDocs,
    IconSelect
  },
  data() {
    return {
      // 遮罩层
      loading: true,
      // 选中数组
      ids: [],
      // 非单个禁用
      single: true,
      // 非多个禁用
      multiple: true,
      // 显示搜索条件
      showSearch: true,
      // 总条数
      total: 0,
      // 主页路由表格数据
      configList: [],
      // 弹出层标题
      title: "",
      // 是否显示弹出层
      open: false,
      typeOptions: [
        {
          dictLabel: "单倍高度",
          dictValue: "50"
        },
        {
          dictLabel: "双倍高度",
          dictValue: "100"
        },
      ],
      // 查询参数
      queryParams: {
        pageNum: 1,
        pageSize: 10,
        title: null,
        type: null,
        key: null,
        icon: null,
        url: null,
      },
      // 表单参数
      form: {},
      // 表单校验
      rules: {
        title: [
          { required: true, message: "配置标题不能为空", trigger: "blur" }
        ],
        interlocutionTitle: [
          { required: true, message: "对话标题不能为空", trigger: "blur" },
          { min: 2, max: 30, message: "对话标题长度应在2到30个字符之间", trigger: "blur" }
        ],
        type: [
          { required: true, message: "卡片类型不能为空", trigger: "change" }
        ],
        key: [
          { required: true, message: "唯一标识不能为空", trigger: "blur" }
        ],
        cueWord: [
          { required: true, message: "开屏提示词不能为空", trigger: "blur" }
        ],
        url: [
          { required: true, message: "跳转路径不能为空", trigger: "blur" }
        ],
      },
      queryP: {
        pageNum:1,
        offset: 0,
        limit: 999,
        name: "",
        graphId: "retrieval_graph",
        metadata: {},
      },
      agentList: [],
      active: 0,
      agentForm: {},
      agentFormIsDis: false,
      xiangLiangForm: {},
      xiangLiangIsDis: false,
      addDataForm: {},
    };
  },
  created() {
    this.getList();
  },
  methods: {
    selected(name) {
      this.form.icon = name;
      console.log(this.form.icon)
      this.$forceUpdate() // 确保视图立即更新
    },
    handleStatusChange(row){
      if(row.status == '0'){
        row.status = '1';
      }else{
        row.status = '0';
      }
      updateConfig(row).then(response => {
        this.$modal.msgSuccess("修改成功");
      });
    },
    /** 查询主页路由列表 */
    getList() {
      this.loading = true;
      listConfig(this.queryParams).then(response => {
        this.configList = response.rows;
        this.total = response.total;
        this.loading = false;
      });
    },
    // 取消按钮
    cancel() {
      this.open = false;
      this.reset();
    },
    // 表单重置
    reset() {
      this.form = {};

      this.xiangLiangForm = {};
      this.xiangLiangIsDis = false;
      this.addDataForm = {}
      this.agentForm = {};
      this.agentFormIsDis = false;
      this.resetForm("form");
      this.active = 0;
    },
    /** 搜索按钮操作 */
    handleQuery() {
      this.queryParams.pageNum = 1;
      this.getList();
    },
    /** 重置按钮操作 */
    resetQuery() {
      this.resetForm("queryForm");
      this.handleQuery();
    },
    // 多选框选中数据
    handleSelectionChange(selection) {
      this.ids = selection.map(item => item.id)
      this.single = selection.length!==1
      this.multiple = !selection.length
    },
    /** 新增按钮操作 */
    handleAdd() {
      this.reset();
      this.open = true;
      this.title = "添加配置";
    },
    /** 修改按钮操作 */
    handleUpdate(row) {
      this.reset();
      const id = row.id || this.ids
      getConfig(id).then(response => {
        this.form = response.data;
        this.open = true;
        this.title = "修改配置";

        // 获取向量数据库
        if(response.data.vectorAssisId){
          langC.agentGet(response.data.vectorAssisId).then(res => {
            res.configStr = JSON.stringify(res.config)
            res.metadataStr = JSON.stringify(res.metadata)
            this.xiangLiangIsDis = true
            this.xiangLiangForm = res;
          });
        }
        // 获取文档信息

        // 获取RAG助手信息
        if(response.data.assisId){
          langC.agentGet(response.data.assisId).then(res => {
            res.config = JSON.parse(JSON.stringify(res.config))
            res.metadata = JSON.stringify(res.metadata)
            this.agentFormIsDis = true
            this.agentForm = res;
          });
        }
      });
    },
    /** 提交按钮 */
    async submitForm() {
      try {
        // 验证基础配置
        await this.$refs.form.validate();
      } catch (error) {
        console.log(1)
        this.active = 0;
        return;
      }
      try {
        // 验证向量数据库
        await this.$refs.xiangLiang.validateForm();
      } catch (error) {
        console.log(12)
        this.active = 1;
        return;
      }
      try {
        // 验证文档
        await this.$refs.addData.validateForm();
      } catch (error) {
        console.log(13)
        this.active = 2;
        return;
      }
      try {
        // 验证助手配置
        await this.$refs.agent.validateForm();
      } catch (error) {
        console.log(14)
        this.active = 3;
        return;
      }

      let xiangLiangRes;
      try {
        // 新增或修改向量数据库
        let formData = this.$refs.xiangLiang.getFormData()
        formData.assistantId = formData.assistant_id
        formData.graphId = formData.graph_id
        if(formData.graph_id!='agent'){
          formData.config = {configurable:formData.config.configurable }
        }else{
          formData.config = JSON.parse(this.form.config) // 只有agent才需要转换，其余都有对应的默认配置
        }
        console.log("submitForm-formData:",formData);
        if (formData.assistant_id != undefined) {
          xiangLiangRes = await langC.agentUpdate(formData.assistant_id, formData);
        } else {
          formData.ifExists = "raise"
          console.log("submitForm-form:",formData);
          xiangLiangRes = await langC.agentCreate(formData); // 添加 await
        }
        console.log("submitForm-xiangLiangRes:",xiangLiangRes);
      } catch (error) {
        this.$modal.msgError("创建向量数据库失败")
        console.log("创建向量数据库失败:",error);
        return;
      }
      
      try {
        console.log(xiangLiangRes)
        // 新增文档之前先将旧文档删除
        await langC.delLangC(xiangLiangRes.config.configurable.collection_name);

        // 新增或修改向量数据库文档
        let formData = this.$refs.addData.getFormData()
        formData.assistantId = xiangLiangRes.assistant_id
        let thread = await langC.threadCreate({
          "thread_id": "",
          "metadata": { graph_id: "indexer", assistantId: formData.assistantId, },
          "if_exists": "raise",
        })
        if (!thread) {
          this.$modal.msgError("创建会话失败")
          this.deleteVector({vectorAssisId:xiangLiangRes.assistant_id,collectionName:xiangLiangRes.collection_name})
          return false
        }
        const docsArr = JSON.parse(formData.docsStr)
        formData.assistant_id = formData.assistantId
        formData.stream_mode = formData.streamMode
        formData.input = {docs:docsArr}
        const res = await fetch("/langC/threads/"+thread.thread_id+"/runs/stream", {
          method: 'post',
          body:JSON.stringify(formData),
          responseType: 'srteam',
          headers: {
            'Content-Type': 'application/json',
          }
        })
      } catch (error) {
        this.deleteVector({vectorAssisId:xiangLiangRes.assistant_id,collectionName:xiangLiangRes.collection_name})
        this.$modal.msgError("创建文档失败")
        console.log("创建文档失败:",error);
        return;
      }

      let agentRes;
      try {
        // 新增或修改助手
        let formData = this.$refs.agent.getFormData()
        if(xiangLiangRes.config.configurable.collection_name !== formData.config.configurable.collection_name){
          throw new Error("向量数据库名称不一致，请重新修改向量数据库名称")
        }
        if(formData.graph_id!='agent'){
          formData.config = {configurable:formData.config.configurable }
        }else{
          formData.config = JSON.parse(formData.config) // 只有agent才需要转换，其余都有对应的默认配置
        }
        const payload = {
          ...formData,
          assistantId: formData.assistant_id,
          graphId: formData.graph_id
        }

        if (formData.assistant_id) {
          agentRes = await langC.agentUpdate(formData.assistant_id, payload)
        } else {
          payload.ifExists = "raise"
          agentRes = await langC.agentCreate(payload)
        }
      } catch (error) {
        this.deleteVector({vectorAssisId:xiangLiangRes.assistant_id,collectionName:xiangLiangRes.collection_name})
        if(error.message=='向量数据库名称不一致，请重新修改向量数据库名称'){
          this.$modal.msgError(error.message)
        }else{
          this.$modal.msgError("创建助手失败")
        }
        console.log("创建助手失败:",error);
        return;
      }

      try {
        // 新增或修改基础信息
        await this.$confirm(this.form.id?'确认修改?':'确认新增?', '提示', {
          confirmButtonText: '确定',
          cancelButtonText: '取消',
          type: 'warning'
        }).then(async () => {
          
          this.form.assisId = agentRes.assistant_id
          this.form.vectorAssisId = xiangLiangRes.assistant_id
          this.form.collectionName = agentRes.config.configurable.collection_name
          if (this.form.id != null) {
            await updateConfig(this.form).then(response => {
              this.$modal.msgSuccess("修改成功");
              this.open = false;
              this.getList();
            });
          } else {
            await addConfig(this.form).then(response => {
              this.$modal.msgSuccess("新增成功");
              this.open = false;
              this.getList();
            });
          }
        }).catch(() => {
          this.$message({
            type: 'info',
            message: '已取消'
          });
          this.deleteVector({vectorAssisId:xiangLiangRes.assistant_id,collectionName:xiangLiangRes.collection_name})
          this.deleteAgent({assisId:agentRes.assistant_id})
        });
      } catch (error) {
        this.deleteVector({vectorAssisId:xiangLiangRes.assistant_id,collectionName:xiangLiangRes.collection_name})
        this.deleteAgent({assisId:agentRes.assistant_id})
        this.$modal.msgError("创建基础信息失败")
        console.log("创建基础信息失败:",error);
      }
    },
    // 删除向量数据库
    deleteVector(row) {
      console.log(row)
      if(row.collectionName!=null&&row.collectionName!=''&&row.collectionName!=undefined){
        langC.delLangC(row.collectionName);
      }
      if(row.vectorAssisId!=null&&row.vectorAssisId!=''&&row.vectorAssisId!=undefined){
        langC.agentDelete(row.vectorAssisId);
      }
    },
    // 删除RAG助手
    deleteAgent(row){
      console.log(row)
      if(row.assisId!=null&&row.assisId!=''&&row.assisId!=undefined){
        langC.agentDelete(row.assisId);
      }
    },
    /** 删除按钮操作 */
    handleDelete(row) {
      const ids = row.id || this.ids;
      this.$modal.confirm('是否确认删除"' + row.title + '"数据项？').then(function() {
        return delConfig(ids);
      }).then(() => {
        this.deleteVector(row)
        this.deleteAgent(row)
        this.getList();
        this.$modal.msgSuccess("删除成功");
      }).catch(() => {});
    },
  }
};
</script>
<style lang="scss" scoped>
.home-config-container {
  padding: 20px;
  min-height: calc(100vh - 84px); // 留出分页空间
  padding-bottom: 80px; // 防止内容被分页遮挡

  .search-wrapper {
    padding: 20px;
    background: #f5f7fa;
    border-radius: 4px;
    margin-bottom: 20px;

    .search-item {
      margin-right: 15px;

      ::v-deep .el-input__inner {
        width: 260px;
      }
    }

    .search-operate {
      float: right;
    }
  }

  .operate-wrapper {
    display: flex;
    justify-content: space-between;
    align-items: center;
    margin-bottom: 20px;

    .left-operate {
      .el-button {
        margin-right: 12px;
      }
    }
  }

  .config-grid {
    min-height: 500px;

    .config-card {
      background: #fff;
      border-radius: 8px;
      margin-bottom: 20px;
      box-shadow: 0 2px 12px 0 rgba(0,0,0,.1);
      transition: transform 0.3s, box-shadow 0.3s;

      &:hover {
        transform: translateY(-3px);
        box-shadow: 0 4px 16px 0 rgba(0,0,0,.12);
      }

      .card-header {
        display: flex;
        align-items: center;
        justify-content: space-between;
        padding: 12px 16px;
        border-bottom: 1px solid #ebeef5;

        .card-index {
          font-size: 14px;
          color: #909399;
        }

        .el-tag {
          font-weight: 500;
        }
      }

      .card-body {
        padding: 16px;

        .card-title {
          margin: 0 0 12px;
          font-size: 16px;
          color: #303133;
          font-weight: 600;
        }

        .card-meta {
          display: flex;
          align-items: center;
          font-size: 13px;

          .meta-label {
            color: #909399;
            flex-shrink: 0;
          }

          .meta-value {
            color: #606266;
            overflow: hidden;
            text-overflow: ellipsis;
            white-space: nowrap;
          }
        }
      }

      .card-footer {
        display: flex;
        align-items: center;
        justify-content: space-between;
        padding: 12px 16px;
        border-top: 1px solid #ebeef5;

        .status-wrapper {
          display: flex;
          align-items: center;

          ::v-deep .el-switch__label {
            color: #909399;
            font-size: 12px;
            margin-left: 6px;

            &.is-active {
              color: #409eff;
            }
          }
        }

        .action-wrapper {
          .el-button {
            padding: 6px 8px;

            &:hover {
              color: #409eff;
            }
          }

          .delete-btn:hover {
            color: #f56c6c;
          }
        }
      }
    }
  }

  // .custom-pagination {
  //   margin-top: 20px;
  //   padding: 12px 16px;
  //   background: #fff;
  //   border-radius: 4px;
  // }

  .fixed-pagination {
    position: fixed;
    right: 20px;
    bottom: 20px;
    z-index: 1000;
    background: #fff;
    padding: 12px 24px;
    border-radius: 28px;
    box-shadow: 0 4px 12px rgba(0, 0, 0, 0.1);
    transition: all 0.3s ease;

    &:hover {
      box-shadow: 0 6px 16px rgba(0, 0, 0, 0.15);
    }

    // 适配移动端
    @media (max-width: 768px) {
      height: 50px;
      left: 50%;
      right: auto;
      transform: translateX(-50%);
      width: 90%;
      text-align: center;
    }
  }

  .config-dialog {
    ::v-deep .el-dialog {
      border-radius: 12px;
      box-shadow: 0 20px 30px rgba(0, 0, 0, 0.1);
      height: 60vh;
      max-height: 60vh;
      display: flex;
      flex-direction: column;
    }

    ::v-deep .el-dialog__header {
      border-radius: 12px 12px 0 0;
      background-color: #f5f7fa;
      padding: 20px 30px;
      border-bottom: 1px solid #ebeef5;

      .el-dialog__title {
        font-size: 18px;
        font-weight: 600;
        color: #303133;
      }
    }

    ::v-deep .el-dialog__body {
      padding: 30px;
      flex: 1;
      overflow-y: auto;
    }

    ::v-deep .el-dialog__footer {
      padding: 20px 30px;
      border-top: 1px solid #ebeef5;
      text-align: right;
      margin: 0;
    }
  }

  ::v-deep .el-steps {
    margin-bottom: 20px;

    .el-step__icon {
      width: 32px;
      height: 32px;
      background-color: #ebeef5;
      border-color: #ebeef5;
      border-radius: 50%;
      transition: background-color 0.3s, border-color 0.3s;

      &.is-process {
        background-color: #409eff;
        border-color: #409eff;

        .el-step__icon-inner {
          color: #fff;
        }
      }

      &.is-finish {
        background-color: #67c23a;
        border-color: #67c23a;

        .el-step__icon-inner {
          color: #fff;
        }
      }
    }

    .el-step__title {
      font-size: 14px;
      color: #303133;
      font-weight: 500;
      transition: color 0.3s;

      &.is-process {
        color: #409eff;
      }

      &.is-finish {
        color: #67c23a;
      }
    }

    .el-step__line {
      background-color: #ebeef5;
      transition: background-color 0.3s;

      &.is-process {
        background-color: #409eff;
      }

      &.is-finish {
        background-color: #67c23a;
      }
    }
  }
}
</style>